This post is a derivation of equation 2 at
wolfram and the equation at the bottom of page 2 in this paper. I have only seen these equations used for determining nth digits of . I would like to share the more general derivation, for explicitly determining any nth digit of any integer base number.
Proof
The equation for a base numbering system is:
Where is the position of the digit to the furthest right side of the number and is the position of the digit to the furthest left side of the number.
A desired can be found with the following steps:
Where is the fractional part of and , this occurs because the maximum value of so:
and:
If the number I am trying to convert is not something like and for measuring real world signals this is okay so I can say
Conclusion
One example of equation is going from a base 10 to a base 2 number. The procedure is to divide the base 10 number by 2 times then take the floor, if it's even then if it's odd then .
An easy example is converting 10.5. 10 is even so . 5 is odd so . 2 is even so . 1 is odd so continuing to divide by 2 and taking the floor always results in 0. Almost done; ; 21 is odd so . Now continuing to multiply by two gets us an even number everytime. So we have:
Applied to an ADC
Using these results to implement an ADC is now straight forward using spice or eesim.dev:
ADC test
.func frac(x)=x-floor(x)
.func A2D(ith)=floor(2*frac(V(1)/2^(ith+1)))
B0 2 0 V= A2D(0)
B1 3 0 V= A2D(1)
B2 4 0 V= A2D(2)
B3 5 0 V= A2D(3)
B4 6 0 V= A2D(4)
Bsum 99 0 V = V(2)*2^0+V(3)*2^1+V(4)*2^2+V(5)*2^3+V(6)*2^4
* DC source for voltage reference
Vs 1 0 dc 0
* DC test
.dc Vs 0 50 0.1
.end
Here I have implemented a 5 bit adc using ngspice's nonlinear element "B"; it allows me to define the voltage which I set to the function in equation . "Bsum" converts the digital signal to an analog one; using both Vs and Bsum I can see how accurate a 5bit ADC is.
Lastly, notice that this is a direct conversion from a base 10 number to a base 2 number. However; in most ADC applications we really want to "bin" values that are between a range. So, lets do this experiment again where the values all land between Vmax and Vmin and and . This can be done by using the binary values that represent less than 1V so:
ADC test
.param Vmax=5 Vmin=0 nth=5
.func frac(x)=x-floor(x)
.func A2D(ith)=floor(2*frac(V(1)/Vmax/2^(ith+1)))
B0 2 0 V= A2D(0-nth)
B1 3 0 V= A2D(1-nth)
B2 4 0 V= A2D(2-nth)
B3 5 0 V= A2D(3-nth)
B4 6 0 V= A2D(4-nth)
Bsum 99 0 V = Vmax*(V(2)*2^(0-nth)+V(3)*2^(1-nth)+V(4)*2^(2-nth)+V(5)*2^(3-nth)+V(6)*2^(4-nth))
* DC source for voltage reference
Vs 1 0 dc 0
* DC test
.dc Vs {Vmin-1} {Vmax+1} {(Vmax-Vmin)/(nth)/100}
.end